/**
 * @author zhuo
 */

import CanvasLayer from "./CanvasLayer";
import clear from "./clear";
import DataSet from "./DataSet";
import drawSimple from "../canvas/draw/simple";

const global = typeof window === "undefined" ? {} : window;
const BMap = global.BMap || global.BMapGL;

class Layer {
  constructor(map, dataSet, options) {
    if (!(dataSet instanceof DataSet)) {
      dataSet = new DataSet(dataSet);
    }
    this.dataSet = dataSet;
    this.map = map;
    var self = this;
    options = options || {};
    self.init(options);
    // 经纬度坐标转为墨卡托坐标
    self.transferToMercator();
    var canvasLayer = (this.canvasLayer = new CanvasLayer({
      map: map,
      context: this.context,
      zIndex: options.zIndex,
      update: function() {
        self._canvasUpdate();
      }
    }));
    canvasLayer._draw();
  }
  init(options) {
    var self = this;
    self.options = options;
    this.context = self.options.context || "2d";

    if (self.options.zIndex) {
      this.canvasLayer && this.canvasLayer.setZIndex(self.options.zIndex);
    }
  }
  // 经纬度左边转换为墨卡托坐标   墨卡托投影 球面经纬度坐标投射成平面坐标
  transferToMercator(dataSet) {
    if (!dataSet) {
      dataSet = this.dataSet;
    }

    var map = this.map;

    var mapType = map.getMapType();
    var projection;
    if (mapType.getProjection) {
      projection = mapType.getProjection();
      console.log(projection, "projection");
    } else {
      projection = {
        lngLatToPoint: function(point) {
          var mc = map.lnglatToMercator(point.lng, point.lat);
          return {
            x: mc[0],
            y: mc[1]
          };
        }
      };
    }

    if (this.options.coordType !== "bd09mc") {
      var data = dataSet.get();

      data = dataSet.transferCoordinate(
        data,
        // 坐标转换方法   经纬度坐标coordinates转换成coordinates_mercator   数据传入坐标点
        function(coordinates) {
          if (
            coordinates[0] < -180 ||
            coordinates[0] > 180 ||
            coordinates[1] < -90 ||
            coordinates[1] > 90
          ) {
            return coordinates;
          } else {
            var pixel = projection.lngLatToPoint({
              // 经度
              lng: coordinates[0],
              // 纬度
              lat: coordinates[1]
            });
            console.log(pixel, "pixel");
            // 像素坐标点
            return [pixel.x, pixel.y];
          }
        },
        // fromColumn
        "coordinates",
        // toColumnName
        "coordinates_mercator"
      );
      dataSet._set(data);
    }
  }
  _canvasUpdate(time) {
    if (!this.canvasLayer) {
      return;
    }

    var self = this;

    var map = this.canvasLayer._map;

    var projection;
    var mcCenter;
    // 设置地图中心点
    if (map.getMapType().getProjection) {
      projection = map.getMapType().getProjection();
      // 坐标转化为点  地图中心点经纬度坐标，转为墨卡托坐标
      mcCenter = projection.lngLatToPoint(map.getCenter());
    } else {
      mcCenter = {
        x: map.getCenter().lng,
        y: map.getCenter().lat
      };
      if (mcCenter.x > -180 && mcCenter.x < 180) {
        mcCenter = map.lnglatToMercator(mcCenter.x, mcCenter.y);
        mcCenter = { x: mcCenter[0], y: mcCenter[1] };
      }
      projection = {
        lngLatToPoint: function(point) {
          var mc = map.lnglatToMercator(point.lng, point.lat);
          return {
            x: mc[0],
            y: mc[1]
          };
        }
      };
    }
    var zoomUnit;
    // 设置地图放大倍数
    if (projection.getZoomUnits) {
      zoomUnit = projection.getZoomUnits(map.getZoom());
    } else {
      zoomUnit = Math.pow(2, 18 - map.getZoom());
    }
    // 左上角墨卡托坐标
    var nwMc = new BMap.Pixel(
      mcCenter.x - (map.getSize().width / 2) * zoomUnit,
      mcCenter.y + (map.getSize().height / 2) * zoomUnit
    );
    var context = this.getContext();
    clear(context);
    // 拷贝option属性，赋值canvas画笔
    if (this.context == "2d") {
      for (var key in self.options) {
        context[key] = self.options[key];
      }
    } else {
      context.clear(context.COLOR_BUFFER_BIT);
    }

    if (
      (self.options.minZoom && map.getZoom() < self.options.minZoom) ||
      (self.options.maxZoom && map.getZoom() > self.options.maxZoom)
    ) {
      return;
    }

    var scale = 1;
    if (this.context != "2d") {
      scale = this.canvasLayer.devicePixelRatio;
    }

    var dataGetOptions = {
      fromColumn:
        self.options.coordType == "bd09mc"
          ? "coordinates"
          : "coordinates_mercator",
      // 坐标转换方法
      // 生成 _coordinates坐标
      transferCoordinate: function(coordinate) {
        var x = ((coordinate[0] - nwMc.x) / zoomUnit) * scale;
        var y = ((nwMc.y - coordinate[1]) / zoomUnit) * scale;
        return [x, y];
      }
    };
    // 从dataSet 获取data
    var data;
    // 得出相对于屏幕得点x,y坐标
    data = self.dataSet.get(dataGetOptions);
    // 根据绘图类型处理data内容
    this.processData(data);
    // 左上角像素位置
    var nwPixel = map.pointToPixel(new BMap.Point(0, 0));
    if (self.options.unit == "m") {
      if (self.options.size) {
        self.options._size = self.options.size / zoomUnit;
      }
      if (self.options.width) {
        self.options._width = self.options.width / zoomUnit;
      }
      if (self.options.height) {
        self.options._height = self.options.height / zoomUnit;
      }
    } else {
      self.options._size = self.options.size;
      self.options._height = self.options.height;
      self.options._width = self.options.width;
    }
    // 绘制内容  self.options用户配置的opitons
    this.drawContext(context, data, self.options, nwPixel);

    //console.timeEnd('draw');

    //console.timeEnd('update')

    // 有回调的话执行回调函数
    self.options.updateCallback && self.options.updateCallback(time);
  }
  // 处理数据
  processData(data) {
    var self = this;
    var draw = self.options.draw;
    if (
      draw == "bubble" ||
      draw == "intensity" ||
      draw == "category" ||
      draw == "choropleth" ||
      draw == "simple"
    ) {
      // 遍历数据
      for (var i = 0; i < data.length; i++) {
        var item = data[i];
        // 如果是泡泡，处理_size
        if (self.options.draw == "bubble") {
          data[i]._size = self.intensity.getSize(item.count);
        } else {
          data[i]._size = undefined;
        }

        var styleType = "_fillStyle";

        if (
          data[i].geometry.type === "LineString" ||
          self.options.styleType === "stroke"
        ) {
          styleType = "_strokeStyle";
        }
        // 如果是强度图，处理_fillStyle
        if (self.options.draw == "intensity") {
          data[i][styleType] = self.intensity.getColor(item.count);
        } else if (self.options.draw == "category") {
          data[i][styleType] = self.category.get(item.count);
        } else if (self.options.draw == "choropleth") {
          data[i][styleType] = self.choropleth.get(item.count);
        }
      }
    }
  }
  getContext() {
    return this.canvasLayer.canvas.getContext(this.context);
  }
  // 画内容
  drawContext(context, dataSet) {
    var self = this;
    switch (self.options.draw) {
      default:
        // 绘制简单点线面方法
        drawSimple.draw(context, dataSet, self.options);
    }
  }
}

export default Layer;
